package com.sample.springbootsample.filter;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import javax.servlet.*;
import java.io.IOException;

/**
 * 过滤器：web.xml中配置
 * 它依赖于servlet容器。在实现上，基于函数回调，它可以对几乎所有请求进行过滤，但是缺点是一个过滤器实例只能在容器初始化时调用一次。
 * 使用过滤器的目的，是用来做一些过滤操作，获取我们想要获取的数据，比如：在Javaweb中，对传入的request、response提前过滤掉一些信息，
 * 或者提前设置一些参数，然后再传入servlet或者Controller进行业务逻辑操作。
 * 通常用的场景是：在过滤器中修改字符编码（CharacterEncodingFilter）、在过滤器中修改HttpServletRequest的一些参数（XSSFilter(自定义过滤器)），
 * 如：过滤低俗文字、危险字符等
 *
 * 拦截器：拦截器的配置一般在SpringMVC的配置文件中，使用Interceptors标签
 * 它依赖于web框架，在SpringMVC中就是依赖于SpringMVC框架。
 * 在实现上,基于Java的反射机制，属于面向切面编程（AOP）的一种运用，就是在service或者一个方法前，调用一个方法，或者在方法后，
 * 调用一个方法，比如动态代理就是拦截器的简单实现，在调用方法前打印出字符串（或者做其它业务逻辑的操作），也可以在调用方法后打印出字符串，
 * 甚至在抛出异常的时候做业务逻辑的操作。由于拦截器是基于web框架的调用，因此可以使用Spring的依赖注入（DI）进行一些业务操作，
 * 同时一个拦截器实例在一个controller生命周期之内可以多次调用。但是缺点是只能对controller请求进行拦截，对其他的一些比如直接访问静态资源的请求则没办法进行拦截处理。
 *
 * 过滤器可以简单理解为"取你所想取"，忽视掉那些你不想要的东西；拦截器可以简单理解为"拒你所想拒"，关心你想要拒绝掉哪些东西
 *
 * @projectName: spring-boot-sample
 * @description:
 * @author: Adam
 * @create: 2019-12-11 22:16
 **/
@Component
public class FilterDemo implements Filter {

    private static Logger logger = LoggerFactory.getLogger(FilterDemo.class);

    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        logger.info("Filter初始化");
    }

    @Override
    public void destroy() {
        logger.info("Filter销毁");
    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        logger.info("do Filter请求处理");
        //链路 直接传给下一个过滤器
        //调用该方法，则web服务器就会调用web资源的service方 法，即web资源就会被访问，否则web资源不会被访问
        filterChain.doFilter(servletRequest, servletResponse);
    }
}
